﻿using IOSendInterface;
using RpcHelper;
using SocketTcpServer.Config;

namespace SocketTcpServer.Model
{
    /// <summary>
    /// 数据包
    /// </summary>
    internal struct DataPage
    {
        /// <summary>
        /// 数据包的类型
        /// </summary>
        public Enum.PageType PageType;

        /// <summary>
        /// 数据类型（1 字符串类型 , 2 实体对象 3 字节流）
        /// </summary>
        public SendType DataType;


        /// <summary>
        /// 数据包的唯一标示
        /// </summary>
        public int DataId;

        /// <summary>
        /// 数据的长度
        /// </summary>
        public int DataLen;

        /// <summary>
        /// 数据包的原始大小(解压时使用)
        /// </summary>
        public int OriginalSize;

        /// <summary>
        /// 是否压缩
        /// </summary>
        public bool IsCompression;
        /// <summary>
        /// 头类型
        /// </summary>
        public byte HeadType;

        /// <summary>
        /// 包的类型(用户自定义)
        /// </summary>
        public char[] Type;

        /// <summary>
        /// 数据内容
        /// </summary>
        public byte[] Content;

        private static byte[] _GetSendStream(Page page)
        {
            if (page.SendData == null)
            {
                return System.Array.Empty<byte>();
            }
            else if (page.SendType == SendType.字节流)
            {
                return (byte[])page.SendData;
            }
            else if (page.SendType == SendType.字符串)
            {
                return ToolsHelper.SerializationString(page.SendData.ToString());
            }
            else
            {
                return ToolsHelper.SerializationClass(page.SendData);
            }
        }
        /// <summary>
        /// 获取数据包的信息
        /// </summary>
        /// <returns></returns>
        public static void InitDataPage(Page page, out DataPage data)
        {
            data = new DataPage
            {
                DataId = page.PageId
            };
            byte[] content = _GetSendStream(page);
            if (SocketConfig.IsCompression && content.LongLength >= Config.SocketConfig.CompressionSize)
            {
                data.IsCompression = true;
                data.OriginalSize = content.Length;
                byte[] myByte = Tools.CompressionData(content);
                data.DataLen = myByte.Length;
                data.Content = myByte;
            }
            else
            {
                data.OriginalSize = content.Length;
                data.Content = content;
                data.DataLen = content.Length;
            }
            data.DataType = page.SendType;
            data.PageType = page.PageType;
            data.Type = page.Type.ToCharArray();
        }
        public int GetPageSize()
        {
            if (this.OriginalSize == 0)
            {
                return this.Type.Length + SocketHelper.HeadLen + 1;
            }
            else
            {
                int len = 1;
                if (this.OriginalSize <= short.MaxValue)
                {
                    if (this.IsCompression)
                    {
                        len += 4;
                        this.HeadType = 3;
                    }
                    else
                    {
                        len += 2;
                        this.HeadType = 2;
                    }
                }
                else if (this.IsCompression)
                {
                    this.HeadType = 5;
                    len += 8;
                }
                else
                {
                    this.HeadType = 4;
                    len += 4;
                }
                return this.Type.Length + len + SocketHelper.HeadLen + this.DataLen;
            }
        }
    }
}
